﻿namespace SecutityLib
{
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;

    /// <summary>
    /// MonoAlphabetic Technique
    /// </summary>
    public class MonoAlphabetic : EncodingDecodingTech
    {
        /// <summary>
        /// Encodes the specified plain text.
        /// </summary>
        /// <param name="plainText">The plain text.</param>
        /// <param name="key">The key.</param>
        /// <returns>cipher text</returns>
        public override string Encode(string plainText, string key)
        {
            string cipher = string.Empty;
            int cnt = plainText.Length;

            if (!this.CheckKey(key))
            {
                throw new System.Exception("key must be 26 unique characters");
            }

            for (int i = 0; i < cnt; i++)
            {
                cipher += key[plainText[i] - 'a'];
            }

            return cipher;
        }

        /// <summary>
        /// Decodes the specified plain text.
        /// </summary>
        /// <param name="cipherText">the cipher text</param>
        /// <param name="key">The key.</param>
        /// <returns>
        /// cipher text
        /// </returns>
        public override string Decode(string cipherText, string key)
        {
            string plain = string.Empty;
            int cnt = cipherText.Length;

            if (!this.CheckKey(key))
            {
                throw new System.Exception("key must be 26 unique characters");
            }

            for (int i = 0; i < cnt; i++)
            {
                for (int j = 0; j < key.Length; j++)
                {
                    if (cipherText[i] == key[j])
                    {
                        plain += (char)(j + 'a');
                        break;
                    }
                }
            }

            return plain;
        }

        /// <summary>
        /// Checks the key.
        /// </summary>
        /// <param name="key">The key.</param>
        /// <returns>true if key format is 26 unique characters</returns>
        private bool CheckKey(string key)
        {
            if (key.Length != 26)
            {
                return false;
            }

            List<char> letters = new List<char>();

            for (int i = 0; i < 26; i++)
            {
                letters.Add((char)('a' + i));
            }

            for (int i = 0; i < 26; i++)
            {
                if (!letters.Remove(key[i]))
                {
                    return false;
                }
            }

            return true;
        }
    }
}
